﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Net.Security;
using System.Runtime.InteropServices;
using System.Security;
using System.Security.Cryptography;
using System.Security.Cryptography.X509Certificates;
using System.Text;
using System.Text.RegularExpressions;
using System.Timers;
using System.Windows.Forms;
using System.Xml;
using bedrock;
using jabber.client;
using jabber.protocol;
using jabber.protocol.client;
using jabber.protocol.iq;

namespace JCore.LoLChat
{
	class Login
	{
		private readonly JabberClient jabberClient = new JabberClient();
		private readonly RosterManager rosterManager = new RosterManager();
		
		public List<Friend> FriendsList = new List<Friend>();

		public List<Friend> Friends = new List<Friend>();
		public List<FriendsInfo> FriendsInfo = new List<FriendsInfo>();
		// public List<> 
		// public BindingList<Class2> bindingList = new BindingList<Class2>();
		// public Dictionary<string, Class2> dictionary = new Dictionary<string, Class2>();

		public void Connect(string username, string password, ISynchronizeInvoke si, int server = 1)
		{
			/*
			 * server can be 0, 1 or 2
			 * 0: NA
			 * 1: EUW
			 * 2: EUEA
			*/
			// Connecting
			try
			{
				AddEventHandlers();
				jabberClient.InvokeControl = si;
				jabberClient.User = username;
				jabberClient.Password = "AIR_jaapjan95";
				// jabberClient.Password = "AIR_" + encryptString(secureString(password));
				jabberClient.Port = 5223;
				jabberClient.SSL = true;
				jabberClient.AutoRoster = true;
				jabberClient.AutoLogin = true;
				jabberClient.AutoPresence = true;
				jabberClient.NetworkHost = "chat.eu.lol.riotgames.com";
				jabberClient.Server = "pvp.net";
				rosterManager.Stream = jabberClient;
				jabberClient.Connect();
			}
			catch (Exception ex)
			{
				MessageBox.Show(ex.Message);
			}
		}

		private void AddEventHandlers()
		{
			// Online Friends (incl. yourself)
			jabberClient.OnPresence += new PresenceHandler(OnPresence);
			
			// All Offline Friends
			rosterManager.OnRosterItem += new RosterItemHandler(OnRosterItem);

			// Activated when he's got all the names in your friend list (kind of 'End of Stream' for OnRosterItem)
			rosterManager.OnRosterEnd += new ObjectHandler(OnRosterEnd);

			// When message received
			jabberClient.OnMessage += new MessageHandler(OnMessage);
			// jabberClient.OnDisconnect += new ObjectHandler(test3);
			// jabberClient.OnAuthError += new ProtocolHandler(test1);
			// jabberClient.OnError += new ExceptionHandler(test1);

			// Certificate Check: not usefull
			jabberClient.OnInvalidCertificate += new RemoteCertificateValidationCallback(certificateCallback);

			/*            
			this.timer_0.Elapsed += new ElapsedEventHandler(this.timer_0_Elapsed);
			this.timer_0.Start();
			*/
		}

		private void OnPresence(object sender, Presence pres)
		{
			/*
			 * -		tempList	Count = 19	System.Collections.Generic.List<string>
		[0]	"506"	string
		[1]	"Whole lotta love"	string
		[2]	"ViktorsCrushers"	string
		[3]	"I"	string
		[4]	"SILVER"	string
		[5]	"RANKED_SOLO_5x5"	string
		[6]	"124"	string
		[7]	"Random"	string
		[8]	"ODIN_UNRANKED"	string
		[9]	"1370641642661"	string
		[10]	"outOfGame"	string
		[11]	"30"	string
		[12]	"1160"	string
		[13]	"50"	string
		[14]	"57"	string
		[15]	"1"	string
		[16]	"0"	string
		[17]	"0"	string
		[18]	"GOLD"	string
			 * */
			// <body><profileIcon>502</profileIcon><level>30</level><wins>182</wins><leaves>1</leaves><odinWins>0</odinWins><odinLeaves>0</odinLeaves><queueType /><rankedLosses>0</rankedLosses><rankedRating>0</rankedRating><tier>UNRANKED</tier><rankedLeagueName>GarensSentries</rankedLeagueName><rankedLeagueDivision>V</rankedLeagueDivision><rankedLeagueTier>BRONZE</rankedLeagueTier><rankedLeagueQueue>RANKED_SOLO_5x5</rankedLeagueQueue><rankedWins>41</rankedWins><statusMsg>3man army</statusMsg><skinname>Rengar</skinname><gameQueueType>NORMAL</gameQueueType><gameStatus>inGame</gameStatus><timeStamp>1370639519908</timeStamp></body>


			// ID = nothing?
			// priority = 0
			// From.User = summ+id


			Regex regex = new Regex(@"<(\w*)>(.*?)</");
			FriendsInfo friendsInfo = new FriendsInfo();

			if (pres.Status != "online" && pres.Status != null)
			{
				foreach (Match match in regex.Matches(pres.Status))
				{
					if (match.Value.Contains("profileIcon"))
					{
						friendsInfo.profileIcon = Int16.Parse(match.Value.Replace(@"</", "").Substring(match.Value.IndexOf('>') + 1).Replace("<profileIcon>", ""));
					}
					else if (match.Value.Contains("level"))
					{
						friendsInfo.level = Int16.Parse(match.Value.Replace(@"</", "").Substring(match.Value.IndexOf('>') + 1).Replace("<profileIcon>", "").Replace("<level>", ""));
					}
					else if (match.Value.Contains("wins"))
					{
						friendsInfo.wins = Int32.Parse(match.Value.Replace(@"</", "").Substring(match.Value.IndexOf('>') + 1).Replace("<profileIcon>", ""));
					}
					else if (match.Value.Contains("statusMsg"))
					{
						friendsInfo.statusMsg =
							match.Value.Replace(@"</", "")
								 .Substring(match.Value.IndexOf('>') + 1)
								 .Replace("<profileIcon>", "");
					}
					else if (match.Value.Contains("gameStatus"))
					{
						friendsInfo.gameStatus = match.Value.Replace(@"</", "")
								 .Substring(match.Value.IndexOf('>') + 1)
								 .Replace("<profileIcon>", "");
					}
					else if (match.Value.Contains("gameQueueType"))
					{
						friendsInfo.gameQueueType = match.Value.Replace(@"</", "")
								 .Substring(match.Value.IndexOf('>') + 1)
								 .Replace("<profileIcon>", "");
					}
					friendsInfo.PvpNetID = pres.From.User;
					Friend temp = new Friend();
					temp.PvpNetID = pres.From.User.Replace("sum", "");
					FriendsList.Add(temp);
				}
				FriendsInfo.Add(friendsInfo);
			}
		}

		private void OnMessage(object sender, jabber.protocol.client.Message msg)
		{
			foreach (Friend friend in Friends)
			{
				if (friend.PvpNetID == msg.From.User)
				{
					_JID = friend.PvpNetID;
					frmLoLProfiler.getInstance().MessageToChatLog(msg.Body, friend.SummonerName, msg.From.User + "@pvp.net");
					if (
						frmLoLProfiler.getInstance().flwLayoutChats.Controls.Find(msg.From.User + "@pvp.net", true).Length ==
						0)
					{
						frmLoLProfiler.getInstance().AddToFlowLayout(friend.SummonerName, msg.From.User);
					}
					// userList.AddUserToFlowLayout(friend.SummonerName);
					break;
				}
			}
		}

		private bool certificateCallback(object sender, X509Certificate certificate, X509Chain chain, SslPolicyErrors sslPolicyErrors)
		{
			return true;
		}

		private void OnRosterItem(object sender, Item item)
		{
			/*
			 * Nickname     = summ-name
			 * Ask          = NONE
			 * JID          = sum*number*@pvp.net
			 * Subscription = both
			 * GetGroups    = groups (General, offline, etc...)
			*/
			Friend friend = new Friend();
			Friend temp = new Friend();

			temp.PvpNetID = item.JID.User.Replace(@"@pvp.net", "").Replace("sum", "");
			FriendsList.Add(temp);

			friend.PvpNetID = item.JID.User.Replace(@"@pvp.net", "");
			friend.SummonerName = item.Nickname;
			Friends.Add(friend);
		}

		private void OnRosterEnd(object sender)
		{
			frmLoLProfiler.getInstance().RefreshOnlineList();
		}

		private string _JID;

		public void SendMessage(string text, string PvpNetID)
		{
			jabberClient.Message(PvpNetID, text);
		}
	}
}
